package com.byinsight.web.actions.util;

import java.util.ArrayList;
import java.util.List;

import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.DefaultHandler;

import com.byinsight.web.actions.Constants;
import com.byinsight.web.actions.ErrorCode;

import eg.backend.domain.Expense;

public class ExpenseParser extends BaseXMLParser{

	private class ExpenseSAXHandler extends DefaultHandler {
		private static final String DELETED = Constants.EXPENSE_DELETE;
		private static final String DIM = Constants.DIM_PREFIX;
		
		private Expense curExpense;
		private boolean deleted = false;
		
		private StringBuilder text = null;
		
		public void startElement(String namespaceURI, String localName,
				String qName, Attributes atts) throws SAXException {
			if (Constants.ROW.equals(localName)) {
				curExpense = new Expense();
			}
			text = new StringBuilder();
		}
		
		public void characters(char[] ch, int start, int length) throws SAXException {
			String value = new String(ch, start, length);
			text.append(value);
		}

		public void endElement(String namespaceURI, String localName, String qName) throws SAXException {
			if (Constants.FIELD_EXP_ID.equalsIgnoreCase(localName)) {
//				Long id = null;
//				try {
//					id = Long.parseLong(text.toString());
//					id = (id < 0) ? null : id;
//				} catch (Exception e) {
//					id = null;
//				}
				curExpense.setId(text.toString());
			} else if (Constants.FIELD_EXP_AMOUNT.equalsIgnoreCase(localName)) {
				Float amount = 0.0F;
				try {
					amount = Float.parseFloat(text.toString());
				} catch (Exception e) {
					amount = 0.0F;
				}
				curExpense.setAmount(amount);
			} else if (Constants.FIELD_EXP_DESC.equalsIgnoreCase(localName)) {
				curExpense.setName(text.toString());
			} else if (Constants.FIELD_EXP_REMARK.equalsIgnoreCase(localName)) {
				curExpense.setRemark(text.toString());
			} else if (Constants.FIELD_EXP_DATE.equalsIgnoreCase(localName)) {
				curExpense.setDate(DateUtil.StringToDate(text.toString()));
			} else if (Constants.FIELD_EXP_TAG.equalsIgnoreCase(localName)) {
				curExpense.setTags(text.toString());
			} else if (Constants.FIELD_EXP_MERCHANT.equalsIgnoreCase(localName)) {
				curExpense.setShopName(text.toString());
			} else if (DELETED.equalsIgnoreCase(localName)) {
				deleted = text.toString().equalsIgnoreCase("true");
			} else if (localName.startsWith(DIM)) {
//				Dimension dim = new Dimension();
//				dim.setId(Long.parseLong(text.toString()));
//				Dimension dim = DimensionHelper.toDimension(localName, text.toString());
				//See DimensionHelper.toDimensionWithTag()
				addDimension(curExpense, text.toString());
			} else if (localName.equalsIgnoreCase(Constants.FIELD_EXP_USER)) {
				curExpense.setOwner(text.toString());
			} else if (Constants.ROW.equalsIgnoreCase(localName)) {
				if (deleted) {
					deletedExpenses.add(curExpense);
				} else {
					updatedExpenses.add(curExpense);
				}
			}
		}
		
		public void startDocument() throws SAXException {
			updatedExpenses = new ArrayList<Expense>();
			deletedExpenses = new ArrayList<Expense>();
		}
		
		private void addDimension(Expense exp, String dimId) {
			exp.addDimension(dimId);
		}
	}
	
	protected DefaultHandler getHandler() {
		return new ExpenseSAXHandler();
	}
	
	protected ErrorCode getParseErrorCode() {
		return ErrorCode.EXPENSE_PARSE_ERROR;
	}
	
	public List<Expense> getUpdatedExpenses() {
		return updatedExpenses;
	}
	public List<Expense> getDeletedExpenses() {
		return deletedExpenses;
	}
	
	
	private List<Expense> updatedExpenses;
	private List<Expense> deletedExpenses;
}
